package com.future.common.jfinalcustom;

import java.lang.reflect.Field;

import com.future.common.annotation.Value;
import com.jfinal.aop.AopFactory;
import com.jfinal.aop.Inject;
import com.jfinal.core.Controller;
import com.jfinal.kit.PropKit;
import com.jfinal.kit.StrKit;
import com.jfinal.plugin.activerecord.Model;
import com.jfinal.validate.Validator;

public class FutureAopFactory extends AopFactory {
	/**
	 * 增加对配置文件值的注入
	 */
	@Override
	protected void doInject(Class<?> targetClass, Object targetObject) throws ReflectiveOperationException {
		targetClass = getUsefulClass(targetClass);
		Field[] fields = targetClass.getDeclaredFields();
		if (fields.length != 0) {
			for (Field field : fields) {
				Class<?> fieldInjectedClass = null;
				Inject inject = field.getAnnotation(Inject.class);
				if(inject != null) {
					 fieldInjectedClass = inject.value();
					if (fieldInjectedClass == Void.class) {
						fieldInjectedClass = field.getType();
					}
					
					Object fieldInjectedObject = doGet(fieldInjectedClass);
					field.setAccessible(true);
					field.set(targetObject, fieldInjectedObject);
				}else {
					Value value = field.getAnnotation(Value.class);
					if(value == null || StrKit.isBlank(value.value())) {
						continue;
					}
					
					String configName = value.value();
					fieldInjectedClass = field.getType();
					field.setAccessible(true);
					if (fieldInjectedClass == String.class) {
						field.set(targetObject, PropKit.get(configName));
					} else if (fieldInjectedClass == Boolean.class || fieldInjectedClass == boolean.class) {
						field.set(targetObject, PropKit.getBoolean(configName));
					} else if (fieldInjectedClass == Integer.class || fieldInjectedClass == int.class) {
						field.set(targetObject, PropKit.getInt(configName));
					} else if (fieldInjectedClass == Long.class || fieldInjectedClass == long.class) {
						field.set(targetObject, PropKit.getLong(configName));
					} else {
						throw new RuntimeException("@Value 注解只支持Long Integer Boolean String 类型的数据注入!");
					}
					
				}
				
				
				
			}
		}
		
		// 是否对超类进行注入
		if (injectSuperClass) {
			Class<?> c = targetClass.getSuperclass();
			if (c != Controller.class && c != Object.class && c != Validator.class && c != Model.class && c != null) {
				doInject(c, targetObject);
			}
		}
	}
}
